package icraf.carbon.gui.model;

import icraf.carbon.core.Project;
import icraf.carbon.core.ProjectIO;
import icraf.carbon.core.Zone;
import icraf.carbon.gui.MatrixPanel;
import icraf.carbon.gui.MenuFactory.MenuProperty;
import icraf.carbon.gui.ProjectManager;
import icraf.carbon.model.ModelProject;
import icraf.common.gui.MenuGenerator;
import icraf.common.gui.MenuGenerator.IconModel;

import java.awt.BorderLayout;
import java.awt.Dimension;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.text.DecimalFormat;
import java.text.NumberFormat;

import javax.swing.BorderFactory;
import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JComboBox;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JTabbedPane;
import javax.swing.JTable;
import javax.swing.JTextField;
import javax.swing.JToolBar;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;

public class ModelSummaryPanel extends JPanel {
	

	public class Listener implements ActionListener, ChangeListener {

		@Override
		public void actionPerformed(ActionEvent e) {
			if (MenuProperty.EDIT_UPDATE.isAction(e)) {
				updateThreshold();
			} else if (MenuProperty.MODEL_CHECKOUT.isAction(e)) {
				checkoutProject();
			} else if (e.getSource().equals(listTypeCB)) {
				int i = listTypeCB.getSelectedIndex();
				if(i == 0) {
					summaryZoneTableModel.setListType(ModelSummaryZoneTableModel.ZONE_SUMMARY);
					valueTypeCB.setEnabled(true);
				} else if(i == 1) {
					summaryZoneTableModel.setListType(ModelSummaryZoneTableModel.DETAIL);
					valueTypeCB.setSelectedIndex(1);
					valueTypeCB.setEnabled(false);
				}
			} else if (e.getSource().equals(valueTypeCB)) {
				int i = valueTypeCB.getSelectedIndex();
//				setCompEnabled(true);
				if(i == 0) {
					summaryZoneTableModel.setValueType(Zone.NET_EMISSION);
				} else if(i == 1) {
					summaryZoneTableModel.setValueType(Zone.EMISSION);
				} else if(i == 2) {
					summaryZoneTableModel.setValueType(Zone.SEQUESTRATION);
					
//				} else if(i == 3) {
//					summaryZoneTableModel.setPercentageOutput(true);
//					setCompEnabled(false);
				}
			} else if (e.getSource().equals(unitTypeCB)) {
				int i = unitTypeCB.getSelectedIndex();
				if(i == 0) {
					summaryZoneTableModel.setTotalPerYear(false);
				} else if(i == 1) {
					summaryZoneTableModel.setTotalPerYear(true);
				}
			}
		}
		
//		private void setCompEnabled(boolean b) {
//			cumulativeCB.setEnabled(b);
//			labelCum.setEnabled(b);
//			unitTypeCB.setEnabled(b);
//			labelUnit.setEnabled(b);
//		}

		@Override
		public void stateChanged(ChangeEvent e) {
			if(e.getSource().equals(eligibleCB)) {
				summaryZoneTableModel.setEligibleOnly(eligibleCB.isSelected());
			} else if(e.getSource().equals(cumulativeCB)) {
				summaryZoneTableModel.setCumulative(cumulativeCB.isSelected());
			}
		}


	}

	private static final long serialVersionUID = 5251033989570690071L;
	private MatrixPanel emissionPanel;
	private DecimalFormat formatter = (DecimalFormat) NumberFormat
			.getNumberInstance();
	private Listener listener = new Listener();
	private Project project;
	private ProjectManager projectManager;
	private MatrixPanel summaryCumPanel;
	private ModelSummaryTableModel summaryCumTableModel = new ModelSummaryTableModel();
	private ModelEmissionTableModel summaryEmissionTableModel = new ModelEmissionTableModel();
	private ModelSummaryZoneTableModel summaryZoneTableModel = new ModelSummaryZoneTableModel();
	private MatrixPanel summaryPanel;
	private MatrixPanel summaryZoneTable;
	private JPanel summaryZonePanel = new JPanel(new BorderLayout());
	private ModelSummaryTableModel summaryTableModel = new ModelSummaryTableModel();
	private JTabbedPane summaryTabPanel = new JTabbedPane();
	private JTextField threshold = new JTextField(5);
	private JCheckBox eligibleCB = new JCheckBox();
	private JCheckBox cumulativeCB = new JCheckBox();
	private JComboBox<String> valueTypeCB;
	private JComboBox<String> listTypeCB;
	private String[] valueTypeStr = {"Net "+MenuProperty.PROJECT_EMISSION.getLabel(), MenuProperty.PROJECT_EMISSION.getLabel(), MenuProperty.PROJECT_SEQUESTRATION.getLabel()};
	private String[] listTypeStr = {MenuProperty.PROJECT_ZONE.getLabel(), MenuProperty.PROJECT_LANDUSE.getLabel()};
	private JComboBox<String> unitTypeCB;
	private String[] unitTypeStr = {MenuProperty.UNIT_EMISSION_HA.getLabel(),
	MenuProperty.UNIT_EMISSION.getLabel()};
	private JLabel labelCum;
	private JLabel labelUnit;
	
	private ModelOutputEmissionNPVPanel outputEmissionNPVPanel = new ModelOutputEmissionNPVPanel();
	
	
	public ModelSummaryPanel() {
		super();

		summaryPanel = new MatrixPanel(summaryTableModel);
		summaryPanel.setDiagonalColor(false);
		summaryCumTableModel.setCumulative(true);
		summaryCumPanel = new MatrixPanel(summaryCumTableModel);
		summaryCumPanel.setDiagonalColor(false);
		
		summaryZoneTable = new MatrixPanel(summaryZoneTableModel);
		summaryZonePanel.add(summaryZoneTable, BorderLayout.CENTER);
		summaryZoneTable.getTable().setAutoCreateRowSorter(true);
		valueTypeCB = new JComboBox<String>(valueTypeStr);
		valueTypeCB.setMaximumSize(new Dimension(100, 20));
		valueTypeCB.addActionListener(listener);
		
		listTypeCB = new JComboBox<String>(listTypeStr);
		listTypeCB.setMaximumSize(new Dimension(100, 20));
		listTypeCB.addActionListener(listener);
		
		unitTypeCB = new JComboBox<String>(unitTypeStr);
		unitTypeCB.setMaximumSize(new Dimension(150, 20));
		unitTypeCB.addActionListener(listener);
		eligibleCB.addChangeListener(listener);
		cumulativeCB.addChangeListener(listener);
		
		//JPanel zoneBarPanel = new JPanel();
		JToolBar zoneBarPanel = new JToolBar();
		zoneBarPanel.setFloatable(false);
		zoneBarPanel.add(listTypeCB);
		zoneBarPanel.addSeparator(new Dimension(20, 20));
		zoneBarPanel.add(new JLabel(MenuProperty.PROJECT_FIELDS.getLabel()+":"));
		zoneBarPanel.add(valueTypeCB);
		zoneBarPanel.addSeparator(new Dimension(20, 20));
		labelUnit = new JLabel(MenuProperty.CHART_AXIS_UNIT.getLabel()+":");
		zoneBarPanel.add(labelUnit);
		zoneBarPanel.add(unitTypeCB);
		zoneBarPanel.addSeparator(new Dimension(20, 20));
		labelCum = new JLabel(MenuProperty.MODEL_CUMULATIVE.getLabel()+":");
		zoneBarPanel.add(labelCum);
		zoneBarPanel.add(cumulativeCB);
		zoneBarPanel.addSeparator(new Dimension(20, 20));
		zoneBarPanel.add(new JLabel(MenuProperty.PROJECT_ELIG_ONLY.getLabel()+":"));
		zoneBarPanel.add(eligibleCB);
		
		summaryZonePanel.add(zoneBarPanel, BorderLayout.NORTH);

		JPanel tPanel = new JPanel(new BorderLayout());
		tPanel.add(createThreshPanel(), BorderLayout.NORTH);
		emissionPanel = new MatrixPanel(summaryEmissionTableModel);
		emissionPanel.getPopMenu().addSeparator();
		emissionPanel.getPopMenu().add(
				MenuGenerator.createMenuItem(MenuProperty.MODEL_CHECKOUT,
						listener));
		emissionPanel.setDiagonalColor(false);
		//emissionPanel.getTable().setAutoResizeMode(JTable.AUTO_RESIZE_SUBSEQUENT_COLUMNS);
		emissionPanel.setBorder(BorderFactory.createEmptyBorder(20, 20, 20, 20));
		
		tPanel.add(emissionPanel);
		tPanel.setBorder(BorderFactory
				.createTitledBorder(MenuProperty.PROJECT_SUMMARY_THRESHOLD_EMISSION
						.getLabel()));

		
		summaryTabPanel.addTab(MenuProperty.PROJECT_SUMMARY.getLabel(), summaryZonePanel);
		
		summaryTabPanel.addTab(MenuProperty.PROJECT_AVOIDED_EMISSION.getLabel(), tPanel);
		summaryTabPanel.addTab(MenuProperty.PROJECT_OPCOST.getLabel(), outputEmissionNPVPanel);
		
		
		summaryTabPanel.addTab(MenuProperty.PROJECT_TOTAL.getLabel(), summaryPanel);
		summaryTabPanel.addTab(MenuProperty.MODEL_CUMULATIVE.getLabel(), summaryCumPanel);
		
		this.setLayout(new BorderLayout());
		this.add(summaryTabPanel);
	}
	
	private void reset() {
		eligibleCB.setSelected(false);
		cumulativeCB.setSelected(false);
		valueTypeCB.setSelectedIndex(0);
		listTypeCB.setSelectedIndex(0);
		unitTypeCB.setSelectedIndex(0);
	}



	public void checkoutProject() {
		JTable table = emissionPanel.getTable();
		if (table.getSelectedRowCount() <= 0)
			return;
		int opt = JOptionPane
				.showConfirmDialog(
						this,
						MenuProperty.MODEL_CHECKOUT_MSG.getAccessibleDescription(),
						MenuProperty.MODEL_CHECKOUT_MSG.getLabel(),
						JOptionPane.OK_CANCEL_OPTION);
		if (opt != JOptionPane.OK_OPTION)
			return;
		int[] rowsselected = table.getSelectedRows();
		for (int r : rowsselected) {
			if (r == 0)
				continue;
			Project p = project.getModelProject().getSimulatedProject(r);
			// TODO: kalo sibling landcover dan cbu nya sama!
			projectManager.add(ProjectIO.duplicateProject(p));
		}
	}

	

	
	
	private JPanel createThreshPanel() {
		JPanel thresP = new JPanel();
		JLabel label = new JLabel(
				MenuProperty.PROJECT_SUMMARY_THRESHOLD.getLabel() + ":");
		JButton bUpdate = MenuGenerator.createButton(MenuProperty.EDIT_UPDATE,
				listener, true, IconModel.ICON16);
		thresP.add(label);
		thresP.add(threshold);
		thresP.add(bUpdate);
		return thresP;
	}

//	public void generateSimulation() {
//		int n = 0;
//		while (n <= 0) {
//			int defN = 1;
//			if (project.getModelProject() != null) {
//				defN = project.getModelProject().getIterationCount();
//			}
//			String inp = (String) JOptionPane.showInputDialog(this,
//					MODEL_GENERATE.getAccessibleDescription() + ":\r\n\""
//							+ project.getLabel() + "\"\r\n"
//							+ "Number of Iterations:",
//					MODEL_GENERATE.getLabel(), JOptionPane.PLAIN_MESSAGE, null,
//					null, defN);
//			if (inp == null)
//				return;
//			try {
//				n = Integer.parseInt(inp);
//			} catch (NumberFormatException excp) {
//				n = -1;
//			}
//		}
//
//		project.generateSimulationModel(n);
//		updateOutput(project.getModelProject());
//	}

	public Project getProject() {
		return project;
	}



	public void setProject(Project project, ProjectManager projectManager) {
		this.project = project;
		this.projectManager = projectManager;
		
		updateOutput(project.getModelProject());
		outputEmissionNPVPanel.setProject(project);
	}

	private void updateOutput(ModelProject mp) {
		summaryTableModel.setModelProject(mp);
		summaryTableModel.fireTableStructureChanged();
		summaryCumTableModel.setModelProject(mp);
		summaryCumTableModel.fireTableStructureChanged();
		summaryEmissionTableModel.setModelProject(mp);
		summaryEmissionTableModel.fireTableStructureChanged();
		summaryZoneTableModel.setModelProject(mp);
		reset();
		
		if(mp !=  null) {
			summaryPanel.getTable().getColumnModel().getColumn(0)
					.setPreferredWidth(300);
			summaryCumPanel.getTable().getColumnModel().getColumn(0)
					.setPreferredWidth(300);
			emissionPanel.getTable().getColumnModel().getColumn(0)
			.setPreferredWidth(100);
			summaryZoneTable.getTable().getColumnModel().getColumn(0)
			.setPreferredWidth(150);
			threshold.setText(formatter.format(mp.getThreshold()));

		}
	}

	public void updateThreshold() {
		double d;
		try {
			d = formatter.parse(threshold.getText()).doubleValue();
			ModelProject m = project.getModelProject();
			m.updateThreshold(d);
			summaryEmissionTableModel.fireTableDataChanged();
		} catch (Exception e1) {
			threshold.setText(formatter.format(project.getModelProject()
					.getThreshold()));

		}

	}


}
